import axios, { AxiosInstance, AxiosRequestConfig, AxiosResponse } from "axios";
import Setting from "../../setting";
import router from "@/router";

// 创建一个错误
function errorCreate(msg: string): void {
    console.error(msg);
    // const err = new Error(msg);
    // throw err;
}

// 记录和显示错误
function errorLog(err: any) {
    console.error(err.message);
}

// 创建一个 axios 实例
const service: AxiosInstance = axios.create({
    // 请求超时时间
    timeout: Setting.apiBaseTime,
    headers: {
        "Content-Type": "application/json"
    }
});

// 请求拦截器
service.interceptors.request.use(
    (config: any) => {
        // 获取Content-Type, 匹配特殊请求方式
        const contentType = config.headers["Content-Type"];

        config.method === "get" || contentType === "multipart/form-data"
            ? (config.params = {
                  ...config.params
              })
            : (config.data = {
                  ...config.data
              });
        return config;
    },
    (error: any) => {
        // 发送失败
        errorLog(error);
        Promise.reject(error);
    }
);

// 响应拦截器
service.interceptors.response.use(
    (response: AxiosResponse<any>) => {
        // dataAxios 是 axios 返回数据中的 data
        const dataAxios = response.data;

        // 这个状态码是和后端约定的
        const { code, msgCode, msg, data } = dataAxios;

        // 如果msgCode有值，说明后台抛出异常，需要在拦截器捕获
        if (msgCode) {
            if (msgCode == 404 || msgCode == 500) {
                errorCreate(`系统异常`);
            } else {
                errorCreate(`[ code: ${msgCode} ] ${msg}`);
            }
        } else {
            // 根据 code 进行判断
            if (!code) {
                // 如果没有 code 代表这不是项目后端开发的接口
                return dataAxios;
            } else {
                // 有 code 代表这是一个后端接口 可以进行进一步的判断
                switch (code) {
                    case 10000:
                        // [ 示例 ] code === 0 代表没有错误
                        return data;
                    case 20001:
                    case 20003:
                        errorCreate(`[ code: ${code} ]:${msg}`);
                        router.push({
                            path: "/login"
                        });
                        return;
                    default:
                        // 不是正确的 code
                        errorCreate(`[ code: ${code} ]:${msg}`);
                        break;
                }
            }
        }
    },
    error => {
        if (error && error.response) {
            switch (error.response.status) {
                case 400:
                    error.message = "请求错误";
                    break;
                case 401:
                    error.message = "未授权，请登录";
                    break;
                case 403:
                    error.message = "拒绝访问";
                    break;
                case 404:
                    error.message = `请求地址出错: ${error.response.config.url}`;
                    break;
                case 408:
                    error.message = "请求超时";
                    break;
                case 500:
                    error.message = "服务器内部错误";
                    break;
                case 501:
                    error.message = "服务未实现";
                    break;
                case 502:
                    error.message = "网关错误";
                    break;
                case 503:
                    error.message = "服务不可用";
                    break;
                case 504:
                    error.message = "网关超时";
                    break;
                case 505:
                    error.message = "HTTP版本不受支持";
                    break;
                default:
                    break;
            }
        }
        errorLog(error);
        return Promise.reject(error);
    }
);

export default service;
